<template>
  <div class="editor">
    <quill-editor
      ref="editorRef"
      v-model:content="editorContent"
      :options="options"
      contentType="html"
    ></quill-editor>
  </div>
</template>

<script setup lang="ts">
  import {
    ref,
    onMounted,
    nextTick,
    defineProps,
    defineEmits,
    watch,
  } from 'vue';
  import { Quill, QuillEditor } from '@vueup/vue-quill';
  import '@vueup/vue-quill/dist/vue-quill.snow.css';
  import { TableModule } from 'quill-table-module';
  import BlotFormatter from 'quill-blot-formatter';
  import axios from 'axios';
  import { getToken } from '@/utils/auth';
  import {
    getindustry,
    getpolicy_direction,
    getpolicydeplist,
  } from '@/api/dataCenter';

  // 注册自定义模块
  Quill.register('modules/table', TableModule);
  Quill.register('modules/blotFormatter', BlotFormatter);

  const props = defineProps({
    modelValue: {
      type: String,
      default: '',
    },
  });

  const emits = defineEmits(['update:modelValue']);
  const editorRef = ref(null);
  const editorContent = ref(props.modelValue || '');

  // 处理富文本图片上传（文件选择器上传）
  const imageHandler = () => {
    const input = document.createElement('input');
    input.setAttribute('type', 'file');
    input.setAttribute('accept', 'image/*');
    input.click();

    input.onchange = async () => {
      const file = input.files ? input.files[0] : null;
      if (file) {
        await uploadImage(file);
      }
    };
  };

  // 上传图片（通用上传函数）
  const uploadImage = async (file: File) => {
    const formData = new FormData();
    formData.append('file', file);

    const url = import.meta.env.VITE_API_BASE_URL + 'global/upload';
    try {
      const res = await axios.post(url, formData, {
        headers: {
          'Content-Type': 'multipart/form-data',
          'Token': getToken(),
        },
      });

      const quill = editorRef.value?.getQuill();
      if (quill) {
        const range = quill.getSelection() || { index: quill.getLength() };
        quill.insertEmbed(
          range.index,
          'image',
          `${import.meta.env.VITE_API_BASE_URL}${res.data[0]}`
        );
        quill.setSelection(range.index + 1);
      }
    } catch (error) {
      console.error('图片上传失败', error);
      alert('图片上传失败');
    }
  };

  // 富文本配置
  const options = ref({
    theme: 'snow',
    modules: {
      toolbar: {
        container: [
          ['bold', 'italic', 'underline', 'strike'],
          [{ color: [] }, { background: [] }],
          [{ align: [] }],
          [{ size: ['small', false, 'large', 'huge'] }],
          [{ font: [] }],
          [{ header: [1, 2, 3, 4, 5, 6, false] }],
          [{ direction: 'ltl' }, { direction: 'rtl' }],
          [{ indent: '-1' }, { indent: '+1' }],
          [{ list: 'ordered' }, { list: 'bullet' }],
          [{ script: 'sub' }, { script: 'super' }],
          ['blockquote', 'code-block'],
          ['clean'],
          ['link', 'image', 'video'],
          ['table'],
        ],
        handlers: {
          image: imageHandler,
          table: (value: boolean) => {
            const quill = editorRef.value?.getQuill();
            if (quill && value) {
              const range = quill.getSelection();
              if (range) {
                const rows = prompt('输入行数', '3');
                const cols = prompt('输入列数', '3');
                if (rows && cols) {
                  const tableHtml = Array.from({ length: parseInt(rows) })
                    .map(
                      () =>
                        `<tr>${Array.from({ length: parseInt(cols) })
                          .map(() => `<td></td>`)
                          .join('')}</tr>`
                    )
                    .join('');
                  quill.clipboard.dangerouslyPasteHTML(
                    range.index,
                    `<table>${tableHtml}</table>`
                  );
                }
              }
            }
          },
        },
      },
      table: {
        operationMenu: {
          items: {
            unmergeCells: { text: '取消合并单元格' },
          },
        },
      },
      clipboard: {
        matchers: [
          // 处理粘贴的表格内容
          [
            'table',
            (node, delta) => {
              const tableHtml = cleanTableNode(node);
              return new Delta().insert(tableHtml, { table: true });
            },
          ],
          // 处理粘贴的图片（改进此处）
          [
            'img',
            (node, delta) => {
              if (node.src.startsWith('data:')) {
                // 检测到Base64格式的粘贴图片，标记并在customPaste中处理
                return new Delta().insert(node.outerHTML, { image: true });
              }
              return delta;
            },
          ],
        ],
      },
      blotFormatter: {
        toolbar: { mainClassName: 'blot-formatter__toolbar' },
      },
    },
  });

  // 清理表格节点并返回HTML
  const cleanTableNode = (node: HTMLElement) => {
    const clone = node.cloneNode(true) as HTMLElement;
    const cleanNode = (el: HTMLElement) => {
      el.removeAttribute('style');
      el.removeAttribute('class');
      el.removeAttribute('width');
      el.removeAttribute('height');
      el.removeAttribute('border');
      el.removeAttribute('cellpadding');
      el.removeAttribute('cellspacing');
      Array.from(el.children).forEach((child) =>
        cleanNode(child as HTMLElement)
      );
    };
    cleanNode(clone);
    if (clone.tagName === 'TABLE') clone.classList.add('ql-table');
    return clone.outerHTML;
  };

  // toolbar标题配置
  const titleConfig = [
    { Choice: '.ql-bold', title: '加粗' },
    { Choice: '.ql-italic', title: '斜体' },
    { Choice: '.ql-underline', title: '下划线' },
    { Choice: '.ql-header', title: '段落格式' },
    { Choice: '.ql-strike', title: '删除线' },
    { Choice: '.ql-blockquote', title: '块引用' },
    { Choice: '.ql-code', title: '插入代码' },
    { Choice: '.ql-code-block', title: '插入代码段' },
    { Choice: '.ql-font', title: '字体' },
    { Choice: '.ql-size', title: '字体大小' },
    { Choice: '.ql-list[value="ordered"]', title: '编号列表' },
    { Choice: '.ql-list[value="bullet"]', title: '项目列表' },
    { Choice: '.ql-direction', title: '文本方向' },
    { Choice: '.ql-header[value="1"]', title: 'h1' },
    { Choice: '.ql-header[value="2"]', title: 'h2' },
    { Choice: '.ql-align', title: '对齐方式' },
    { Choice: '.ql-color', title: '字体颜色' },
    { Choice: '.ql-background', title: '背景颜色' },
    { Choice: '.ql-image', title: '图像' },
    { Choice: '.ql-video', title: '视频' },
    { Choice: '.ql-link', title: '添加链接' },
    { Choice: '.ql-formula', title: '插入公式' },
    { Choice: '.ql-clean', title: '清除字体格式' },
    { Choice: '.ql-script[value="sub"]', title: '下标' },
    { Choice: '.ql-script[value="super"]', title: '上标' },
    { Choice: '.ql-indent[value="-1"]', title: '向左缩进' },
    { Choice: '.ql-indent[value="+1"]', title: '向右缩进' },
    { Choice: '.ql-header .ql-picker-label', title: '标题大小' },
    { Choice: '.ql-header .ql-picker-item[data-value="1"]', title: '标题一' },
    { Choice: '.ql-header .ql-picker-item[data-value="2"]', title: '标题二' },
    { Choice: '.ql-header .ql-picker-item[data-value="3"]', title: '标题三' },
    { Choice: '.ql-header .ql-picker-item[data-value="4"]', title: '标题四' },
    { Choice: '.ql-header .ql-picker-item[data-value="5"]', title: '标题五' },
    { Choice: '.ql-header .ql-picker-item[data-value="6"]', title: '标题六' },
    { Choice: '.ql-header .ql-picker-item:last-child', title: '标准' },
    { Choice: '.ql-size .ql-picker-item[data-value="small"]', title: '小号' },
    { Choice: '.ql-size .ql-picker-item[data-value="large"]', title: '大号' },
    { Choice: '.ql-size .ql-picker-item[data-value="huge"]', title: '超大号' },
    { Choice: '.ql-size .ql-picker-item:nth-child(2)', title: '标准' },
    { Choice: '.ql-align .ql-picker-item:first-child', title: '居左对齐' },
    {
      Choice: '.ql-align .ql-picker-item[data-value="center"]',
      title: '居中对齐',
    },
    {
      Choice: '.ql-align .ql-picker-item[data-value="right"]',
      title: '居右对齐',
    },
    {
      Choice: '.ql-align .ql-picker-item[data-value="justify"]',
      title: '两端对齐',
    },
    { Choice: '.ql-table', title: '插入表格' },
  ];

  // 初始化工具栏提示
  const initTitle = () => {
    for (let item of titleConfig) {
      const tip = document.querySelector('.editor .ql-toolbar ' + item.Choice);
      if (tip) tip.setAttribute('title', item.title);
    }
  };

  // 自定义粘贴处理（关键改进点）
  const customPaste = (e) => {
    e.preventDefault();
    const clipboardData = e.clipboardData;
    const types = Array.from(clipboardData.types);
    const quill = editorRef.value?.getQuill();

    if (!quill) return;

    const range = quill.getSelection() || { index: quill.getLength() };

    // 处理图片粘贴（从剪贴板直接粘贴图片）
    if (types.includes('Files')) {
      const files = Array.from(clipboardData.files);
      const imageFiles = files.filter((file) => file.type.startsWith('image/'));

      if (imageFiles.length > 0) {
        imageFiles.forEach((file) => uploadImage(file));
        return;
      }
    }

    // 处理HTML格式粘贴（可能包含Base64图片）
    if (types.includes('text/html')) {
      const html = clipboardData.getData('text/html');

      // 检查是否包含Base64图片
      if (html.includes('data:image')) {
        // 创建临时元素解析HTML
        const tempDiv = document.createElement('div');
        tempDiv.innerHTML = html;
        const images = tempDiv.querySelectorAll('img');

        if (images.length > 0) {
          // 提取Base64图片并上传
          Array.from(images).forEach((img, index) => {
            if (img.src.startsWith('data:image')) {
              // 将Base64转换为Blob
              const base64Data = img.src.split(',')[1];
              const byteString = atob(base64Data);
              const mimeString = img.src
                .split(',')[0]
                .split(':')[1]
                .split(';')[0];
              const ab = new ArrayBuffer(byteString.length);
              const ia = new Uint8Array(ab);

              for (let i = 0; i < byteString.length; i++) {
                ia[i] = byteString.charCodeAt(i);
              }

              const blob = new Blob([ab], { type: mimeString });
              const file = new File(
                [blob],
                `clipboard-image-${Date.now()}-${index}.png`,
                { type: mimeString }
              );
              uploadImage(file);
            }
          });
          return;
        }
      }
    }

    // 处理普通文本/表格粘贴
    if (types.includes('text/html')) {
      const cleanHtml = html.includes('<table') ? cleanTableHtml(html) : html;
      quill.clipboard.dangerouslyPasteHTML(range.index, cleanHtml);
    } else if (types.includes('text/plain')) {
      const text = clipboardData.getData('text/plain');
      quill.insertText(range.index, text);
      quill.setSelection(range.index + text.length);
    }
  };

  // 清理并规范化表格HTML
  const cleanTableHtml = (html: string) => {
    try {
      const tempDoc = new DOMParser().parseFromString(html, 'text/html');
      const tables = tempDoc.querySelectorAll('table');

      tables.forEach((table) => {
        table.removeAttribute('style');
        table.removeAttribute('border');
        table.removeAttribute('cellpadding');
        table.removeAttribute('cellspacing');
        table.classList.add('ql-table');

        const cells = table.querySelectorAll('td, th');
        cells.forEach((cell) => {
          cell.removeAttribute('style');
          cell.removeAttribute('width');
          cell.removeAttribute('height');
          const emptyPs = cell.querySelectorAll('p');
          emptyPs.forEach((p) => {
            if (!p.textContent.trim() && p.children.length === 0) p.remove();
          });
        });
      });

      return tempDoc.body.innerHTML;
    } catch (error) {
      console.error('表格解析错误:', error);
      return html;
    }
  };

  // 监听内容变化
  watch(editorContent, (newVal) => {
    emits('update:modelValue', newVal);
  });

  // 监听外部prop变化
  watch(
    () => props.modelValue,
    (newVal) => {
      if (newVal !== editorContent.value) {
        editorContent.value = newVal;
      }
    },
    { immediate: true }
  );

  onMounted(() => {
    nextTick(() => {
      initTitle();

      const quill = editorRef.value?.getQuill();
      if (quill) {
        quill.root.addEventListener('paste', (e) => {
          customPaste(e);
        });

        if (quill.getModule('table')) {
          console.log('表格模块已初始化');
        }
      }
    });
  });
</script>

<style scoped lang="less">
  .editor {
    width: 100%;

    ::v-deep .ql-editor {
      min-height: 200px;
      font-size: 16px;
      line-height: 1.6;
    }

    ::v-deep table {
      border-collapse: collapse;
      width: 100%;
      margin: 10px 0;
    }

    ::v-deep td,
    ::v-deep th {
      border: 1px solid #ddd;
      padding: 8px;
      min-width: 60px;
    }

    ::v-deep th {
      background-color: #f2f2f2;
      font-weight: bold;
    }

    ::v-deep img {
      max-width: 100%;
      height: auto;
      display: block;
      margin: 10px 0;
      cursor: move; /* 提示图片可拖动 */
    }

    ::v-deep .ql-editor {
      overflow-y: auto;
      max-height: 400px;

      &::-webkit-scrollbar {
        width: 6px;
      }

      &::-webkit-scrollbar-track {
        background: #f1f1f1;
        border-radius: 10px;
      }

      &::-webkit-scrollbar-thumb {
        background: #c1c1c1;
        border-radius: 10px;
      }

      &::-webkit-scrollbar-thumb:hover {
        background: #a1a1a1;
      }
    }

    ::v-deep .ql-table-cell-selected {
      background-color: rgba(0, 123, 255, 0.1);
    }
  }
</style>
